package org.mika.asm;

import java.lang.reflect.Method;
import java.util.HashMap;
import java.util.Map;

import net.sf.cglib.proxy.Enhancer;
import net.sf.cglib.proxy.MethodInterceptor;
import net.sf.cglib.proxy.MethodProxy;

/**
 * Very fast introspector.
 * @author mika
 */
public final class Introspector implements MethodInterceptor {
	private Introspector() {}
	
	private static Map<String, Class<? extends BeanWalker>> cache;
	
	static {
		cache = new HashMap<String, Class<? extends BeanWalker>>();
	}
	
	@SuppressWarnings("unchecked")
	public static void iterate(Object bean, BeanIterator iterator) throws Exception {
		synchronized (Introspector.class) {
			if(!cache.containsKey(bean.getClass().getName())) {
				Enhancer e = new Enhancer();
				e.setStrategy(new BeanIteratorWorkerGenerator(bean.getClass()));
				e.setCallbackType(Introspector.class);
				e.setUseCache(false);
				e.setUseFactory(false);
				cache.put(bean.getClass().getName(), e.createClass());
			}
		}
		cache.get(bean.getClass().getName()).getConstructor(bean.getClass()).newInstance(
			bean
		).walk(iterator);
	}

	@Override
	public Object intercept(Object arg0, Method arg1, Object[] arg2, MethodProxy arg3) throws Throwable {
		return null;
	}
}
